package aggregate

import (
	"context"

	"gitee.com/leonscript/sally/v2/domain/entity"
	"gorm.io/gorm"
)

// Reference 聚合所有仓储接口
type Reference interface {
	TX
	WorkflowRepository
	NodeRepository
	ReviewTaskRepository
}

// TX 事物
type TX interface {
	// Begin 创建事物
	Begin() *gorm.DB
	Commit(tx *gorm.DB) error
	Rollback(tx *gorm.DB) error
}

// WorkflowRepository 工作流仓储接口
type WorkflowRepository interface {
	QueryWorkflowTemplateByID(ctx context.Context, id string) (result entity.WorkflowTemplate, err error)
	CreateWorkflowTemplateTX(ctx context.Context, workflowTemplate entity.WorkflowTemplate, tx *gorm.DB) (err error)
	CreateWorkflowTX(ctx context.Context, workflow entity.Workflow, tx *gorm.DB) (err error)
	QueryAndLockWorkflowByCondTX(ctx context.Context, cond QueryWorkflowCond, tx *gorm.DB) (result entity.Workflow, err error)
	UpdateWorkflow(ctx context.Context, workflow entity.Workflow) (err error)
	UpdateWorkflowTX(ctx context.Context, workflow entity.Workflow, tx *gorm.DB) (err error)
	QueryActivatedWorkflows(ctx context.Context, req GetWorkflowsRequest) (result []ActivatedWorkflow, total int64, err error)
	QueryWorkflowByID(ctx context.Context, id string) (result entity.Workflow, err error)
	DeleteWorkflowByCondTX(ctx context.Context, id string, tx *gorm.DB) (err error)
}

// NodeRepository 节点仓储接口
type NodeRepository interface {
	CreateNodeTX(ctx context.Context, node entity.Node, tx *gorm.DB) (err error)
	CreateNodeTemplateTX(ctx context.Context, nodeTemplate entity.NodeTemplate, tx *gorm.DB) (err error)
	CreateNodeTemplateReviewersTX(ctx context.Context, reviewers []entity.NodeTemplateReviewer, tx *gorm.DB) (err error)
	QueryNodeTemplateByID(ctx context.Context, id string) (result entity.NodeTemplate, err error)
	UpdateNodeTX(ctx context.Context, node entity.Node, tx *gorm.DB) (err error)
	QueryNodeTemplateReviewers(ctx context.Context, nodeTemplateID string) (result []entity.NodeTemplateReviewer, err error)
	QueryNodeByIDTX(ctx context.Context, id string, tx *gorm.DB) (result entity.Node, err error)
	DeleteNodeByCondTX(ctx context.Context, workflowID string, tx *gorm.DB) (err error)
	// QueryNodeTemplatesByWorkflowTemplateID 根据工作流模板ID查询所有节点模板
	QueryNodeTemplatesByWorkflowTemplateID(ctx context.Context, workflowTemplateID string) (result []entity.NodeTemplate, err error)
	// QueryNodesByWorkflowID 根据工作流ID查询所有节点
	QueryNodesByWorkflowID(ctx context.Context, workflowID string) (result []entity.Node, err error)
	// QueryNodeTemplateReviewersByNodeTemplateID 根据节点模板ID查询所有审批人
	QueryNodeTemplateReviewersByNodeTemplateID(ctx context.Context, nodeTemplateID string) (result []entity.NodeTemplateReviewer, err error)
	// QueryNodeTemplateReviewersByNodeTemplateIDs 根据节点模板ID列表批量查询所有审批人
	QueryNodeTemplateReviewersByNodeTemplateIDs(ctx context.Context, nodeTemplateIDs []string) (result []entity.NodeTemplateReviewer, err error)
}

// ReviewTaskRepository 审批任务仓储接口
type ReviewTaskRepository interface {
	CreateReviewerTasksTX(ctx context.Context, reviewerTasks []entity.NodeReviewerTask, tx *gorm.DB) (err error)
	QueryReviewerTaskByID(ctx context.Context, id string) (result entity.NodeReviewerTask, err error)
	UpdateNodeReviewerTaskTX(ctx context.Context, nodeReviewerTask entity.NodeReviewerTask, tx *gorm.DB) (err error)
	UpdateNodeReviewerTaskByCondTX(ctx context.Context, cond, nodeReviewerTask entity.NodeReviewerTask, tx *gorm.DB) (err error)
	QueryNodeReviewTasks(ctx context.Context, req GetNodeReviewTasksRequest) (result []NodeReviewTask, total int64, err error)
	QueryNodeReviewTasksTX(ctx context.Context, req GetNodeReviewTasksRequest, tx *gorm.DB) (result []NodeReviewTask, err error)
	DeleteNodeReviewerTaskByCondTX(ctx context.Context, workflowID string, tx *gorm.DB) (err error)
	// QueryNodeReviewerTasksByNodeIDTX 根据节点ID查询所有审批任务
	QueryNodeReviewerTasksByNodeIDTX(ctx context.Context, nodeID string, tx *gorm.DB) (result []entity.NodeReviewerTask, err error)
	// QueryNodeReviewerTaskByIDTX 根据任务ID查询审批任务（事务版本）
	QueryNodeReviewerTaskByIDTX(ctx context.Context, id string, tx *gorm.DB) (result entity.NodeReviewerTask, err error)
}

type QueryWorkflowCond struct {
	ReviewerTaskID string
	WorkflowID     string
}
